# -*- coding: utf-8 -*-
# @Time    : 2023/2/7 13:52
# @Author  : kali
import datetime

from database_init import db


class SerializerAbleMixin(object):

    def to_dict(self, *args, is_except=False, is_hump=False):
        """
        序列化
        :param args: 自定义序列化字段
        :param is_except: 序列化是否根据args排除字段
        :param is_hump: 返回是否用驼峰命名
        :return: dict
        """
        value = dict()
        for column in self.__table__.columns:
            attribute = getattr(self, column.name)
            if isinstance(attribute, datetime.datetime):
                attribute = str(attribute)
            if is_hump is True:
                column_name = self.__hump(column.name)
            else:
                column_name = column.name
            if not args:
                value[column_name] = attribute
            else:
                if is_except is False:
                    if column.name in args:
                        value[column_name] = attribute
                else:
                    if column.name not in args:
                        value[column_name] = attribute
        return value

    def from_dict(self, attributes):
        """Update the current instance base on attribute->value by *attributes*"""
        for attribute in attributes:
            setattr(self, attribute, attributes[attribute])
        return self

    def __hump(self, column_name):
        column_list = column_name.split('_')
        for key in range(len(column_list)):
            if key != 0:
                column_list[key] = column_list[key].capitalize()
        return ''.join(column_list)


class BaseModel(object):
    """
    基础模型
    """
    id = db.Column(db.Integer, index=True, primary_key=True, autoincrement=True, comment="数据库ID")
    create_time = db.Column(db.DateTime, default=datetime.datetime.now, comment="创建时间")
    update_time = db.Column(db.DateTime, default=datetime.datetime.now, comment="更新时间")

    def save(self):
        db.session.add(self)
        db.session.commit()

    def update(self):
        db.session.commit()

    def find(self, **kwargs):
        match_dict = {}
        for k, v in kwargs.items():
            if not hasattr(self, k):
                continue
            match_dict[k] = v
        rows = db.session.execute(db.select(self.__class__.__name__).filter_by(**match_dict)).scalar()
        return rows


class Tags(BaseModel, db.Model, SerializerAbleMixin):
    """
    标签/分类模型
    """
    tag = db.Column(db.String(100), index=True, unique=True, nullable=False, comment="标签名称")
    tag_url = db.Column(db.String(200), nullable=False, comment="标签地址")
    introduction = db.Column(db.Text, nullable=False, comment="标签简介")
    questions = db.Column(db.BigInteger, nullable=False, comment="问题总数")
    today_asked = db.Column(db.BigInteger, nullable=False, comment="今日新增问题数量")
    week_asked = db.Column(db.BigInteger, nullable=False, comment="本周新增问题数量")


class TagsHistory(BaseModel, db.Model, SerializerAbleMixin):
    """
    标签采集的历史记录，一天只有一条记录，用于统计
    """
    tag = db.Column(db.String(100), index=True, unique=True, nullable=False, comment="标签名称")
    questions = db.Column(db.BigInteger, nullable=False, comment="问题总数")
    today_asked = db.Column(db.BigInteger, nullable=False, comment="今日新增问题数量")
    week_asked = db.Column(db.BigInteger, nullable=False, comment="本周新增问题数量")
    date = db.Column(db.String(20), nullable=False, comment="日期")


class Question(BaseModel, db.Model, SerializerAbleMixin):
    """
    问题模型
    """
    web_id = db.Column(db.String(100), index=True, unique=True, nullable=False, comment="问题在网站的ID")
    url = db.Column(db.String(200), nullable=False, comment="问题详情链接")
    title = db.Column(db.Text, nullable=False, comment="标题")
    asked = db.Column(db.String(100), nullable=False, comment="提问时间")
    modified = db.Column(db.String(100), nullable=False, comment="活跃时间")
    question = db.Column(db.Text, nullable=False, comment="问题详情，HTML内容")
    tags = db.Column(db.String(100), nullable=False, comment="所属标签")
    viewed = db.Column(db.BigInteger, nullable=False, comment="访问数量")
    votes = db.Column(db.BigInteger, nullable=False, comment="投票数量")
    answers = db.Column(db.BigInteger, nullable=False, comment="回答数量")
    asker_name = db.Column(db.String(100), nullable=False, comment="提问用户")
    asker_url = db.Column(db.String(200), nullable=False, comment="提问用户空间链接")
